﻿using FieldController.Interfaces;
using OpenQA.Selenium;
using OpenQA.Selenium.Chrome;
using OpenQA.Selenium.DevTools.V137.Accessibility;
using OpenQA.Selenium.DevTools.V137.Debugger;
using OpenQA.Selenium.Interactions;
using OpenQA.Selenium.Support.UI;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Controls.Primitives;
using SeleniumExtras.WaitHelpers;
using OpenQA.Selenium.Support.Events;

namespace FieldController.Impls
{
    public class FieldGet : IFieldGet
    {
        public string Company { get; set; }
        public string Name { get; set; }
        public string Phone { get; set; }

        ChromeDriver driver { get; set; }


        public ChromeOptions Config()
        {
            ChromeOptions Opt = new ChromeOptions();
            Opt.AddExcludedArgument("enable-automation");//关闭安全提示
            Opt.AddAdditionalOption("useAutomationExtension", false);
            ////Opt.AddArgument("--start-mximized");//启动最大化
            Opt.AddArgument("--DisableCommandResponse-Popup-blocking");//禁用弹出拦截
            //Opt.AddArgument("no-sandbox");//关闭沙盘
            //Opt.AddArgument("disable-extensions");//扩展插件检测
            //Opt.AddArgument("no-default-browser-check");//默认浏览器检测


            //禁用GPU加速，避免在某些系统上出现问题
            //Opt.AddArgument("--disable-gpu");
            //Opt.AddArgument("--disable-software-rasterizer");
            // 禁用沙箱，在以高权限（如Administrator）运行时可能需要
            //Opt.AddArgument("--no-sandbox");
            // 禁用/dev/shm共享内存使用，在Docker或某些Linux环境中常见问题
            //Opt.AddArgument("--disable-dev-shm-usage");
            // 忽略证书错误
            Opt.AddArgument("--ignore-certificate-errors");
            //启动时最大化窗口，确保元素可见
            Opt.AddArgument("--start-maximized");

            Opt.BinaryLocation = @"C:\Users\24019\AppData\Local\Google\Chrome\Application\chrome.exe"; // Windows 示例

            //// 隐藏“Chrome正在受到自动软件控制”的信息栏（虽然通常不影响，但更清爽）
            //Opt.AddExcludedArgument("enable-automation");

            ////Opt.AddArgument("--no-sandbox");   // 禁用沙盒（有时在特定环境下需要）
            //Opt.AddArgument("--disable-dev-shm-usage"); // 使用/dev/shm以外的共享内存

            ////如果问题依旧，可以尝试更彻底的禁用方式
            //Opt.AddArgument("--use-gl=swiftshader");// 使用SwiftShader软件渲染
            //// 或者
            //Opt.AddArgument("--use-angle=swiftshader"); // 使用ANGLE的SwiftShader后端



            // 如果您的问题依旧，可以尝试启用日志记录来调试
            // Opt.SetLoggingPreference(LogType.Driver, LogLevel.All);

            Company = "广州微远基因科技有限公司";
            Name = "黄贤玉";
            Phone = "13760687233";


            return Opt;
        }



        public async Task Test()
        {
            var Opt = Config();
            //var chromeDriverService = ChromeDriverService.CreateDefaultService();//关闭黑窗口
            var chromeDriverService = ChromeDriverService.CreateDefaultService("C:\\Users\\24019\\AppData\\Local\\Google\\Chrome\\Application\\chromedriver.exe"); // 可执行文件名

            driver = new ChromeDriver(chromeDriverService, Opt);

            try
            {
                driver.Navigate().GoToUrl("https://www.baidu.com/");

                // 显式等待元素出现，而不是使用固定的 Task.Delay
                await Task.Delay(4000);

                // 刷新页面
                driver.Navigate().Refresh(); // [1,2,4](@ref)
                //var wait = new WebDriverWait(driver, TimeSpan.FromSeconds(10));
                //var conText = wait.Until(drv => drv.FindElement(By.Id("kw")));
                ////var conText = wait.Until(ExpectedConditions.ElementIsVisible(By.Id("kw")));
                //conText.SendKeys("美女");
                //await Task.Delay(100);

                //// 等待搜索按钮可点击
                //var souBtn = wait.Until(drv => drv.FindElement(By.Id("su")));
                //souBtn.Click();

                var wait = new WebDriverWait(driver, TimeSpan.FromSeconds(10));
                // 等待元素存在、可见并可交互（例如，等待输入框）
                //var conText = wait.Until(ExpectedConditions.ElementIsVisible(By.Id("wd")));

                await Task.Delay(2000);

                // var conText = wait.Until(ExpectedConditions.ElementIsVisible(By.Id("kw")));
                // conText.SendKeys("美女");

                // //等待搜索按钮可点击后再点击
                //var souBtn = wait.Until(ExpectedConditions.ElementIsVisible(By.Id("su")));
                // souBtn.Click();


                var souBtn = wait.Until(ExpectedConditions.ElementIsVisible(By.Id("chat-submit-button")));
                souBtn.Click();

                await Task.Delay(100);

                // 如果需要，可以等待某个搜索结果元素出现，确认跳转完成
                // await Task.Delay(100); // 通常更推荐显式等待 (WebDriverWait) 而不是固定延迟
            }
            catch (Exception ex)
            {
                Console.WriteLine($"执行过程中发生错误: {ex.Message}");
                // 根据需要处理异常，例如记录日志或重试
                // 注意：异步方法中抛出的异常会被捕获并存储在返回的Task中
            }
        }


        public async Task GetFieldTest()
        {
            var Opt = Config();
            var chromeDriverService = ChromeDriverService.CreateDefaultService("C:\\Users\\24019\\AppData\\Local\\Google\\Chrome\\Application\\chromedriver.exe");//关闭黑窗口

            driver = new ChromeDriver(chromeDriverService, Opt);
            await Task.Delay(200);
            driver.Manage().Timeouts().PageLoad = TimeSpan.FromSeconds(5);// 设置30秒页面加载超时
            await Task.Delay(20);
            driver.Navigate().GoToUrlAsync("https://jsj.top/f/e6ITjv");
            await Task.Delay(200);
            driver.Navigate().RefreshAsync(); // [1,2,4](@ref)
            //await Task.Delay(200);
            try
            {
                // 刷新页面
                //driver.Navigate().Refresh(); // [1,2,4](@ref)

                // 创建一个通用的WebDriverWait实例，设置10秒超时
                var wait = new WebDriverWait(driver, TimeSpan.FromSeconds(10));

                var radioOption = wait.Until(ExpectedConditions.ElementToBeClickable(
                By.XPath("//label[.//input[@name='field_5' and @value='GQI6']]")
                ));
                radioOption.Click();

                // 等待第一个输入框出现并可见（而不仅仅是存在于DOM中）
                var conText = wait.Until(ExpectedConditions.ElementIsVisible(By.Id("TextInputfield_1")));
                conText.SendKeys(Company);

                // 等待第二个输入框出现并可见
                var conText2 = wait.Until(ExpectedConditions.ElementIsVisible(By.Id("TextInputfield_2")));
                conText2.SendKeys(Name); // 注意：这里原代码错用了conText，应改为conText2

                // 等待第三个输入框出现并可见 field_3
                var conText3 = wait.Until(ExpectedConditions.ElementIsVisible(By.Name("field_3")));
                conText3.SendKeys(Phone); // 注意：这里原代码错用了conText，应改为conText3

                //var radioOption = wait.Until(ExpectedConditions.ElementToBeClickable(By.CssSelector("input[type='radio'][value='GQI6']")));
                // 等待包含目标radio的label可点击，通过“后代input的name和value”定位label

                //radioLabel.click();

                //点击了radio后 combox才会出现

                // 首先，定位到下拉框的触发按钮或容器，点击以展开选项列表
                //var dropdownTrigger = wait.Until(ExpectedConditions.ElementToBeClickable(By.XPath("//*[@id=\"rc_select_8\"]")));
                //var dropdownTrigger = wait.Until(ExpectedConditions.ElementToBeClickable(
                //By.XPath("//div[contains(@class, 'ant-select') and .//input[@id='rc_select_8']]")
                //));
                // 假设ID绑定在外部容器
                //                var dropdownTrigger = wait.Until(ExpectedConditions.ElementToBeClickable(
                //    By.XPath("//*[@aria-owns='rc_select_8_list']")
                //));
                //await Task.Delay(5000);

                wait.PollingInterval = TimeSpan.FromMilliseconds(300); // 设置轮询间隔为300毫秒
                wait.IgnoreExceptionTypes(typeof(NoSuchElementException)); // 忽略元素不存在的异常
                await Task.Delay(500);
                var dropdownTrigger = driver.FindElement(By.XPath("//*[@id=\"rc_select_0\"]"));
                dropdownTrigger.Click();

                // 2. 等待下拉选项列表可见
                // 根据aria-owns属性，列表的ID可能是'rc_select_0_list'（注意：动态ID可能变化）
                //IWebElement dropdownList = wait.Until(SeleniumExtras.WaitHelpers.ExpectedConditions.ElementIsVisible(By.Id("rc_select_0_list"))); // 请替换为实际ID
                //var dropdownList = driver.FindElements(By.Id("rc_select_0_list")); // 请替换为实际ID


                // 3. 在下拉列表中定位并点击想要的选项（例如通过选项文本定位）
                // 假设要选择文本为“选项文本”的选项
                await Task.Delay(500);
                var desiredOption = driver.FindElements(
                    By.XPath(".//div[contains(@class, 'ant-select-item')]")); // 请替换为实际选项文本
                desiredOption[4].Click();
                await Task.Delay(500);

                wait.PollingInterval = TimeSpan.FromMilliseconds(300); // 设置轮询间隔为300毫秒
                wait.IgnoreExceptionTypes(typeof(NoSuchElementException)); // 忽略元素不存在的异常
                var dropdownTrigger2 = driver.FindElement(By.XPath("//*[@id=\"rc_select_1\"]"));
                dropdownTrigger2.Click();
                await Task.Delay(500);
                //desiredOption[8].Click();

                var Submit = driver.FindElement(By.XPath("//*[@id=\"root\"]/div/form/div[4]/div/button"));
                Submit.Click();
                //*[@id="root"]/div/form/div[4]/div/button
                //var dropdownTrigger = wait.Until(ExpectedConditions.ElementToBeClickable(
                //    By.XPath("//*[contains(@id, 'rc_select_')]") // 这可能会找到父元素
                //));
                ;
                //var dropdownTrigger = wait.Until(ExpectedConditions.ElementToBeClickable(By.CssSelector("div.ant-select[id=\"rc_select_0\"]")));
                // 如果找到的是父元素，而不是input本身，你可能需要在此基础上再向下查找
                //if (!dropdownTrigger.TagName.Equals("input"))
                //{
                //    // 例如，从找到的父元素里寻找input子元素
                //    dropdownTrigger = dropdownTrigger.FindElement(By.CssSelector("input.ant-select-selection-search-input"));
                //}


                // 等待选项列表出现
                //var optionMenu = wait.Until(ExpectedConditions.ElementIsVisible(By.CssSelector("div.ant-select-dropdown")));

                // 然后，在出现的选项列表中定位到你想要的特定选项并点击它
                // 以下是根据选项的文本内容进行定位的示例，假设要选择文本为“Option Text”的选项


                //var desiredOption = wait.Until(ExpectedConditions.ElementToBeClickable(By.XPath("//div[contains(@class, 'ant-select-item-option') and contains(text(), 'Option Text')]")));

                //desiredOption.Click();


                await Task.Delay(100);

                // 如果需要，可以等待某个搜索结果元素出现，确认跳转完成
                // await Task.Delay(100); // 通常更推荐显式等待 (WebDriverWait) 而不是固定延迟
            }
            catch (Exception ex)
            {
                Console.WriteLine($"执行过程中发生错误: {ex.Message}");
                throw new Exception("执行过程中发生错误");
                // 根据需要处理异常，例如记录日志或重试
                // 注意：异步方法中抛出的异常会被捕获并存储在返回的Task中
            }
        }

        public async Task ReadyGetField()
        {
            var Opt = Config();
            var chromeDriverService = ChromeDriverService.CreateDefaultService("C:\\Users\\24019\\AppData\\Local\\Google\\Chrome\\Application\\chromedriver.exe");//关闭黑窗口


            driver = new ChromeDriver(chromeDriverService, Opt);
            await Task.Delay(200);
            driver.Manage().Timeouts().PageLoad = TimeSpan.FromSeconds(5);// 设置30秒页面加载超时
            await Task.Delay(20);
            driver.Navigate().GoToUrlAsync("https://jsj.top/f/e6ITjv");
            await Task.Delay(200);
        }

        public async Task GetField()
        {



            //// 显式等待元素出现，而不是使用固定的 Task.Delay
            //var wait = new WebDriverWait(driver, TimeSpan.FromSeconds(10));
            //var conText = wait.Until(drv => drv.FindElement(By.Id("TextInputfield_1")));
            //conText.SendKeys(Company);
            //await Task.Delay(100);

            //var wait2 = new WebDriverWait(driver, TimeSpan.FromSeconds(10));
            //var conText2 = wait.Until(drv => drv.FindElement(By.Id("TextInputfield_2")));
            //conText.SendKeys(Name);
            //await Task.Delay(100);

            //var wait3 = new WebDriverWait(driver, TimeSpan.FromSeconds(10));
            //var conText3= wait.Until(drv => drv.FindElement(By.Id("TextInputfield_3")));
            //conText.SendKeys(Phone);
            //await Task.Delay(100);

            // 等待搜索按钮可点击
            //var souBtn = wait.Until(drv => drv.FindElement(By.Id("su")));
            //souBtn.Click();

            driver.Navigate().RefreshAsync(); // [1,2,4](@ref)
            //await Task.Delay(200);
            try
            {
                // 刷新页面
                //driver.Navigate().Refresh(); // [1,2,4](@ref)

                // 创建一个通用的WebDriverWait实例，设置10秒超时
                var wait = new WebDriverWait(driver, TimeSpan.FromSeconds(10));

                //var radioOption = wait.Until(ExpectedConditions.ElementToBeClickable(
                //By.XPath("//label[.//input[@name='field_5' and @value='GQI6']]")
                //));

                var radioOption = wait.Until(ExpectedConditions.ElementToBeClickable(
                By.XPath("//label[.//input[@name='field_5' and @value='28ZK']]")
                ));
                radioOption.Click();

                // 等待第一个输入框出现并可见（而不仅仅是存在于DOM中）
                var conText = wait.Until(ExpectedConditions.ElementIsVisible(By.Id("TextInputfield_1")));
                conText.SendKeys(Company);

                // 等待第二个输入框出现并可见
                var conText2 = wait.Until(ExpectedConditions.ElementIsVisible(By.Id("TextInputfield_2")));
                conText2.SendKeys(Name); // 注意：这里原代码错用了conText，应改为conText2

                // 等待第三个输入框出现并可见 field_3
                var conText3 = wait.Until(ExpectedConditions.ElementIsVisible(By.Name("field_3")));
                conText3.SendKeys(Phone); // 注意：这里原代码错用了conText，应改为conText3

                //var radioOption = wait.Until(ExpectedConditions.ElementToBeClickable(By.CssSelector("input[type='radio'][value='GQI6']")));
                // 等待包含目标radio的label可点击，通过“后代input的name和value”定位label

                //radioLabel.click();

                //点击了radio后 combox才会出现

                // 首先，定位到下拉框的触发按钮或容器，点击以展开选项列表
                //var dropdownTrigger = wait.Until(ExpectedConditions.ElementToBeClickable(By.XPath("//*[@id=\"rc_select_8\"]")));
                //var dropdownTrigger = wait.Until(ExpectedConditions.ElementToBeClickable(
                //By.XPath("//div[contains(@class, 'ant-select') and .//input[@id='rc_select_8']]")
                //));
                // 假设ID绑定在外部容器
                //                var dropdownTrigger = wait.Until(ExpectedConditions.ElementToBeClickable(
                //    By.XPath("//*[@aria-owns='rc_select_8_list']")
                //));
                //await Task.Delay(5000);

                wait.PollingInterval = TimeSpan.FromMilliseconds(300); // 设置轮询间隔为300毫秒
                wait.IgnoreExceptionTypes(typeof(NoSuchElementException)); // 忽略元素不存在的异常
                await Task.Delay(500);
                var dropdownTrigger = driver.FindElement(By.XPath("//*[@id=\"rc_select_0\"]"));
                dropdownTrigger.Click();

                // 2. 等待下拉选项列表可见
                // 根据aria-owns属性，列表的ID可能是'rc_select_0_list'（注意：动态ID可能变化）
                //IWebElement dropdownList = wait.Until(SeleniumExtras.WaitHelpers.ExpectedConditions.ElementIsVisible(By.Id("rc_select_0_list"))); // 请替换为实际ID
                //var dropdownList = driver.FindElements(By.Id("rc_select_0_list")); // 请替换为实际ID


                // 3. 在下拉列表中定位并点击想要的选项（例如通过选项文本定位）
                // 假设要选择文本为“选项文本”的选项
                await Task.Delay(500);
                var desiredOption = driver.FindElements(
                    By.XPath(".//div[contains(@class, 'ant-select-item')]")); // 请替换为实际选项文本
                desiredOption[4].Click();
                await Task.Delay(500);

                wait.PollingInterval = TimeSpan.FromMilliseconds(300); // 设置轮询间隔为300毫秒
                wait.IgnoreExceptionTypes(typeof(NoSuchElementException)); // 忽略元素不存在的异常
                var dropdownTrigger2 = driver.FindElement(By.XPath("//*[@id=\"rc_select_1\"]"));
                dropdownTrigger2.Click();
                await Task.Delay(500);
                //desiredOption[8].Click();

                var Submit = driver.FindElement(By.XPath("//*[@id=\"root\"]/div/form/div[4]/div/button"));
                Submit.Click();
            }
            catch (Exception ex)
            {
                Console.WriteLine($"执行过程中发生错误: {ex.Message}");
                throw new Exception("执行过程中发生错误");
                // 根据需要处理异常，例如记录日志或重试
                // 注意：异步方法中抛出的异常会被捕获并存储在返回的Task中
            }
        }
    }
 
}
